package com.bootdo.system.controller;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.Set;

import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.AuthenticationException;
import org.apache.shiro.authc.UsernamePasswordToken;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.apache.shiro.subject.Subject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;

import com.bootdo.common.annotation.Log;
import com.bootdo.common.controller.BaseController;
import com.bootdo.common.domain.Tree;
import com.bootdo.common.utils.MD5Utils;
import com.bootdo.common.utils.PageUtils;
import com.bootdo.common.utils.Query;
import com.bootdo.common.utils.R;
import com.bootdo.system.domain.MenuDO;
import com.bootdo.system.domain.SysUserDO;
import com.bootdo.system.domain.UserTokenDO;
import com.bootdo.system.service.MenuService;
import com.bootdo.system.service.RoleService;
import com.bootdo.system.service.UserService;
import com.github.pagehelper.PageInfo;

import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;

@RequestMapping("/sys/user")
@Controller
@Api(value = "/sys/user", description = "用户操作接口")
public class UserController extends BaseController {
	@Autowired
	UserService userService;
	@Autowired
	RoleService roleService;
	@Autowired
	MenuService menuService;

	@ApiOperation(value="用户查询", notes="", response=String.class)
	@ApiImplicitParams({
        @ApiImplicitParam(name = "id", value = "前台用户地址id", required = false,paramType="query", dataType = "Long"),
        @ApiImplicitParam(name = "roleName", value = "角色名称", required = false,paramType="query", dataType = "String"),
        @ApiImplicitParam(name = "pageSize", value = "每页条数", required = true,paramType="query", dataType = "Integer"),
        @ApiImplicitParam(name = "pageNum", value = "当前页数", required = true,paramType="query", dataType = "Integer")
	})
	@GetMapping("/list")
	@ResponseBody
	R list(@RequestParam Map<String, Object> params)  throws Exception{
		 Query query = new Query(params);
			List<SysUserDO> address = userService.list(query);
			for(SysUserDO user : address) {
				List<Long> roleList = new ArrayList<Long>();
				Set<String> roles  =userService.listRoles(user.getUserId());
				if(roles != null) {
					for(String roleId: roles) {
						roleList.add(Long.valueOf(roleId));
					}
				}
				user.setroleIds(roleList);
			}
			PageInfo<SysUserDO> pageInfo = new PageInfo<SysUserDO>(address);
			int total = (int)pageInfo.getTotal();
			PageUtils pageUtil = new PageUtils(address, total);
			return new R("list",pageUtil);
	}


	@ApiOperation(value="用户详情", notes="", response=String.class)
	@ApiImplicitParams({
        @ApiImplicitParam(name = "id", value = "用户id", required = true,paramType="query", dataType = "Long"),
	})
	@GetMapping("/edit")
	@ResponseBody
	R edit(Long id)  throws Exception{
		SysUserDO userDO = userService.get(id);
		List<Long> roleList = new ArrayList<Long>();
		Set<String> roles  =userService.listRoles(userDO.getUserId());
		if(roles != null) {
			for(String roleId: roles) {
				roleList.add(Long.valueOf(roleId));
			}
		}
		userDO.setroleIds(roleList);
		return new R("obj",userDO);
	}

	@ApiOperation(value="用户保存", notes="", response=String.class)
	@PostMapping("/save")
	@ResponseBody
	R save(@RequestBody SysUserDO user)  throws Exception{
		try {
			user.setPassword(MD5Utils.encrypt(user.getUsername(), user.getPassword()));
			if (userService.save(user) > 0) {
				return R.saveOk(user.getUserId()+"");
			}
			return R.error();
		}catch(Exception e) {
			e.printStackTrace();
			return R.error();
		}
	}

	@ApiOperation(value="用户更新", notes="", response=String.class)
	@PostMapping("/update")
	@ResponseBody
	R update(@RequestBody SysUserDO user)  throws Exception{
		user.setPassword(MD5Utils.encrypt(user.getUsername(), user.getPassword()));
		if (userService.update(user) > 0) {
			return R.ok();
		}
		return R.error();
	}

	@ApiOperation(value="用户删除", notes="", response=String.class)
	@ApiImplicitParams({
        @ApiImplicitParam(name = "id", value = "用户id", required = true,paramType="query", dataType = "Long"),
	})
	@GetMapping("/remove")
	@ResponseBody
	R remove(Long id)  throws Exception{
		if (userService.remove(id) > 0) {
			return R.ok();
		}
		return R.error();
	}

	@RequiresPermissions("sys:user:batchRemove")
	@Log("批量删除用户")
	@PostMapping("/batchRemove")
	@ResponseBody
	R batchRemove(@RequestParam("ids[]") Long[] userIds)  throws Exception{
		if ("test".equals(getUsername())) {
			return R.error(1, "演示系统不允许修改,完整体验请部署程序");
		}
		List<Long> Ids = Arrays.asList(userIds);
		int r = userService.batchremove(Ids);
		System.out.println(r);
		if (r > 0) {
			return R.ok();
		}
		return R.error();
	}

	@PostMapping("/exit")
	@ResponseBody
	boolean exit(@RequestParam Map<String, Object> params)  throws Exception{
		// Query query = new Query(params);
		return !userService.exit(params);// 存在，不通过，false
	}


	@ApiOperation(value="用户登录", notes="通过用户名和密码登录", response=String.class)
	@ApiImplicitParams({
        @ApiImplicitParam(name = "userName", value = "用户名", required = true,paramType="query", dataType = "String"),
        @ApiImplicitParam(name = "password", value = "密码", required = true,paramType="query", dataType = "String")
	})
	@GetMapping("/login")
	@ResponseBody
	R login(@RequestParam Map<String, Object> params)  throws Exception{
		try {
		String userName = params.get("userName")+"";
		String password = MD5Utils.encrypt(userName, params.get("password")+"");
		SysUserDO user = userService.login(userName,password);
		if (user != null) {
			List<Long> roleList = new ArrayList<Long>();
			Set<String> roles  =userService.listRoles(user.getUserId());
			if(roles != null) {
				for(String roleId: roles) {
					roleList.add(Long.valueOf(roleId));
				}
			}
			user.setroleIds(roleList);
			Long tokenId = userService.getTokenId(user.getUserId());
			if(tokenId == null) {
				UserTokenDO ut = new UserTokenDO();
				ut.setUserId(user.getUserId());
				ut.setUserName(user.getUsername());
				ut.setCreateTime(new Date());
				ut.setDeadTime(1000L);
				int res = userService.saveToken(ut);
				tokenId = ut.getId();
			}
			List<Tree<MenuDO>> tree = menuService.listMenuTree(user.getUserId());
			R r = new R();
			r.put("user",user);
			r.put("tokenId", tokenId);
			r.put("menu", tree);
			return r;
		}
		}catch(Exception e) {
			e.printStackTrace();
		}
		return R.error("用户名或密码错误");
	}

}
